/*
 * Copyright (c) 2013-2015 Charkey. All rights reserved.
 *
 * This software is the confidential and proprietary information of Charkey.
 * You shall not disclose such Confidential Information and shall use it only
 * in accordance with the terms of the agreements you entered into with Charkey.
 *
 * Charkey MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF THE SOFTWARE,
 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR NON-INFRINGEMENT.
 *
 * Charkey SHALL NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING,
 * MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
 */

package cn.simastudio.talos.common.utils.codec;

import org.apache.commons.codec.binary.Base64;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.crypto.*;
import javax.crypto.spec.SecretKeySpec;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

/**
 * Usage: AES对称加密工具类
 *
 * @author Charkey
 * @date 2015/6/27 16:28
 */
public class AESUtils {

    public static final String ALGORITHM_NAME = "AES";

    private static final Logger LOGGER = LoggerFactory.getLogger(AESUtils.class);

    public static String encrypt(String secretKey, String content) {
        try {
            // 还原密钥
            SecretKey secret = new SecretKeySpec(Base64.decodeBase64(secretKey), ALGORITHM_NAME);
            // 创建密码器
            Cipher cp = Cipher.getInstance("AES/ECB/PKCS5Padding");
            // 初始化
            cp.init(Cipher.ENCRYPT_MODE, secret);
            // 加密
            byte[] encryptStr = cp.doFinal(content.getBytes());
            return Base64.encodeBase64String(encryptStr);
        } catch (NoSuchAlgorithmException | IllegalBlockSizeException | BadPaddingException | NoSuchPaddingException | InvalidKeyException e) {
            if (LOGGER.isErrorEnabled()) {
                LOGGER.error("Encrypt error: {}", e);
            }
        }
        return "";
    }

    public static String decrypt(String secretKey, String content) {
        try {
            // 还原密钥
            SecretKey secret = new SecretKeySpec(Base64.decodeBase64(secretKey), ALGORITHM_NAME);
            // 创建密码器
            Cipher cp = Cipher.getInstance("AES/ECB/PKCS5Padding");
            // 初始化
            cp.init(Cipher.DECRYPT_MODE, secret);
            // 解密
            byte[] decryptStr = cp.doFinal(Base64.decodeBase64(content));
            return new String(decryptStr);
        } catch (NoSuchAlgorithmException | NoSuchPaddingException | BadPaddingException | IllegalBlockSizeException | InvalidKeyException e) {
            if (LOGGER.isErrorEnabled()) {
                LOGGER.error("Decrypt error: {}", e);
            }
        }
        return "";
    }

    public static String initAESKey() {
        try {
            // KeyGenerator类用于获得各类对称加密技术的密钥
            // 初始化HmacMD5摘要算法的密钥产生器，设置要获得的密钥的加密算法
            KeyGenerator generator = KeyGenerator.getInstance(ALGORITHM_NAME);
            // 初始化
            generator.init(128);
            // 产生密钥，从对称加密的密钥对象中取得密钥
            SecretKey secretKey = generator.generateKey();
            // 获得密钥
            return new String(Base64.encodeBase64(secretKey.getEncoded()));
        } catch (NoSuchAlgorithmException e) {
            if (LOGGER.isErrorEnabled()) {
                LOGGER.error("initAESKey error: {}", e);
            }
        }
        return null;
    }

    public static void main(String[] args) {
        String keyString = initAESKey();
        System.out.println("Key: " + keyString);

        String content = "Charkey";

        String encryptedContent = encrypt(keyString, content);
        System.out.println("Encrypted Content: " + encryptedContent);

        String decryptContent = decrypt(keyString, encryptedContent);
        System.out.println("Decrypted Content: " + decryptContent);
    }
}
